home *** CD-ROM | disk | FTP | other *** search
/ Mac-Source 1994 July / Mac-Source_July_1994.iso / C and C++ / Entertainment / MacMud / unixlib.c < prev   
Encoding:
C/C++ Source or Header  |  1992-03-31  |  14.0 KB  |  571 lines  |  [TEXT/MPS ]

  1. #include <sys/time.h>
  2. #include <sys/types.h>
  3. #include <sys/timeb.h>
  4. #include <Events.h>
  5. #include <OSUtils.h>
  6. #include <FCntl.h>
  7. #include <types.h>
  8. #include <ToolUtils.h>
  9. #include <strings.h>  /* for c2pstr */
  10. #include <Files.h>
  11. #include <Errors.h>
  12.  
  13. extern int errno;
  14.  
  15. /*
  16.  * unix getwd
  17.  *
  18.  *    where must point to 256 bytes
  19.  *    
  20.  *    work up from the current directory to the root collecting 
  21.  *    name segments as we go
  22.  */
  23.  
  24. char *getwd(char *where)
  25. {
  26.     WDPBRec pb;
  27.     CInfoPBRec cpb;
  28.     char wdtemp[256],*start,*store,*trav;
  29.     int i;
  30.  
  31.     /* get default volume and directory last set by PBSetVol or PBHSetVol */
  32.     pb.ioNamePtr = where;
  33.     PBHGetVol(&pb,false);
  34.  
  35.     /* add a colon */
  36.     (*where)++;
  37.     where[*where] = ':';
  38.     
  39.     trav = wdtemp; /* build name here */
  40.     cpb.dirInfo.ioCompletion = 0L;
  41.  
  42.     cpb.dirInfo.ioVRefNum = pb.ioWDVRefNum; /* vRefNum of volume on which */
  43.                                             /* working dir exists */
  44.     
  45.     cpb.dirInfo.ioDrDirID = pb.ioWDDirID; /* directory ID of working directory */
  46.     
  47.     while(cpb.dirInfo.ioDrDirID != 0) 
  48.     {
  49.         cpb.hFileInfo.ioNamePtr = trav; /* put name segment here */
  50.         cpb.hFileInfo.ioFDirIndex = -1;
  51.         if (PBGetCatInfo(&cpb,false) != 0)  
  52.         {
  53.             cpb.dirInfo.ioDrDirID = 0;
  54.             break;
  55.         }
  56.         if (*trav == 0) 
  57.         {
  58.             cpb.dirInfo.ioDrDirID=0;
  59.             break;
  60.         }
  61.         i=*trav;      /* save length */
  62.         *trav=0;      /* null over length */
  63.         start=trav+1; /* addr of 1st char */
  64.         trav+=i+1;    /* point past current string for next name segment */ 
  65.         *trav=0;      /* initially zero length */
  66.  
  67.         cpb.dirInfo.ioDrDirID = cpb.dirInfo.ioDrParID; /* point up to parent directory */
  68.     }
  69.     
  70.     *wdtemp=0;
  71.     store=where+*where+1; /* start storing after volume name */
  72.     
  73.     if (trav-wdtemp) 
  74.         *where=(trav-wdtemp); /* set length of where as length of trav */
  75.     if (trav!=wdtemp) 
  76.         start=trav-1; 
  77.     else 
  78.         start=wdtemp;
  79.  
  80.     if (start!=wdtemp) 
  81.     {
  82.         while(*start) start--;        /* Go to beginning of string */
  83.         if (start!=wdtemp) 
  84.             start--;
  85.     }
  86.  
  87.     while(start!=wdtemp) 
  88.     {
  89.         while(*start) /* Go to beginning of string */
  90.             start--;        
  91.         trav=start+1; 
  92.         while (*trav)  /* store it */
  93.         {
  94.             *store=*trav; 
  95.             store++;
  96.             trav++; 
  97.         } 
  98.         *store=':';    /* Ready to move directory name */
  99.         store++;
  100.         if (start!=wdtemp) 
  101.             start--;
  102.         *store=0;
  103.     }    
  104.     return(p2cstr(where));
  105. }
  106.  
  107. /*
  108.  * unix change working directory
  109.  */
  110. static int currentWD = 0;
  111.  
  112. int chdir(char *pathName)
  113. {
  114.     WDPBRec pb;
  115.     char tempst[256];
  116.     long default_ioWDDirID;
  117.     short wdToClose;
  118.  
  119.     /* 
  120.      * get default volume last set by PBSetVol or PBHSetVol 
  121.      */
  122.     pb.ioNamePtr = 0L;
  123.     PBHGetVol(&pb,false);
  124.     default_ioWDDirID = pb.ioWDDirID;
  125.  
  126.     /*
  127.      * create a new mac working directory using the default volume and
  128.      * the callers partial pathname
  129.      */
  130.     strcpy(tempst,pathName);
  131.     pb.ioNamePtr = (char *)c2pstr(tempst);
  132.     pb.ioVRefNum = 0;
  133.     pb.ioWDDirID = default_ioWDDirID;
  134.     pb.ioCompletion = 0L;
  135.     pb.ioWDProcID = 'UTCS';
  136.  
  137.     if ((errno = PBOpenWD(&pb,0)) != noErr) 
  138.         return(-1);
  139.     
  140.     /*
  141.      * make the mac working directory which has just been created in 'pb'
  142.      * the new default directory. destroy the mac working directory which
  143.      * was the previous default.
  144.      */
  145.     if ((errno = setvol(0L, pb.ioVRefNum)) != noErr) 
  146.     {
  147.         wdToClose = pb.ioVRefNum;
  148.     } 
  149.     else 
  150.     {
  151.         wdToClose = currentWD;
  152.         currentWD = pb.ioVRefNum;
  153.     }
  154.  
  155.     /*
  156.      * close the previous working directory
  157.      */
  158.     if (wdToClose == 0)    /* nothing more to do, return */
  159.         return(0);
  160.  
  161.     pb.ioVRefNum = wdToClose;
  162.     pb.ioCompletion = 0L;
  163.     (void) PBCloseWD(&pb, false); /* ignore error */
  164.     
  165.     return(0);
  166. }
  167.  
  168. /*
  169.  * Mac version of Unix system call gettimeofday. 
  170.  *
  171.  * Time is converted to the Unix epoch: Jan 1, 1970.
  172.  *
  173.  * The current timezone is always GMT.
  174.  */
  175.  
  176. static struct DateTimeRec unixEpochDtr = {1970,1,1, 0,0,0, 1};
  177. gettimeofday(tp,tzp) struct timeval *tp; struct timezone *tzp;
  178. {
  179.  
  180.     unsigned long unixEpochSecs,currentMacSecs;
  181.     
  182.     Date2Secs(&unixEpochDtr,&unixEpochSecs);
  183.     GetDateTime(¤tMacSecs);
  184.     tp->tv_sec = currentMacSecs - unixEpochSecs;
  185.     tp->tv_usec = 0;
  186.  
  187.     if (tzp != NULL)
  188.     {
  189.         tzp->tz_minuteswest = 0;    /* minutes west of Greenwich */
  190.         tzp->tz_dsttime = 0;    /* no dst correction */
  191.     }
  192. }
  193.  
  194. #if 0
  195. /*
  196.  * Backwards compatible time call.
  197.  */
  198. time_t
  199. time(t)
  200.     time_t *t;
  201. {
  202.     struct timeval tt;
  203.  
  204.     if (gettimeofday(&tt, (struct timezone *)0) < 0)
  205.         return (-1);
  206.     if (t)
  207.         *t = tt.tv_sec;
  208.     return (tt.tv_sec);
  209. }
  210. #endif
  211.  
  212.  
  213. /*
  214.  * The arguments are the number of minutes of time
  215.  * you are westward from Greenwich and whether DST is in effect.
  216.  * It returns a string
  217.  * giving the name of the local timezone.
  218.  *
  219.  * Sorry, I don't know all the names.
  220.  */
  221.  
  222. static struct zone {
  223.     int    offset;
  224.     char    *stdzone;
  225.     char    *dlzone;
  226. } zonetab[] = {
  227.     -1*60, "MET", "MET DST",    /* Middle European */
  228.     -2*60, "EET", "EET DST",    /* Eastern European */
  229.     4*60, "AST", "ADT",        /* Atlantic */
  230.     5*60, "EST", "EDT",        /* Eastern */
  231.     6*60, "CST", "CDT",        /* Central */
  232.     7*60, "MST", "MDT",        /* Mountain */
  233.     8*60, "PST", "PDT",        /* Pacific */
  234. #ifdef notdef
  235.     /* there's no way to distinguish this from WET */
  236.     0, "GMT", 0,            /* Greenwich */
  237. #endif
  238.     0*60, "WET", "WET DST",        /* Western European */
  239.     -10*60, "EST", "EST",        /* Aust: Eastern */
  240.     -10*60+30, "CST", "CST",    /* Aust: Central */
  241.     -8*60, "WST", 0,        /* Aust: Western */
  242.     -9*60, "JST", 0,        /* Japanese */
  243.     -1
  244. };
  245.  
  246. char *timezone(zone, dst)
  247. {
  248.     register struct zone *zp;
  249.     static char czone[10];
  250.     char *sign;
  251.     register char *p, *q;
  252.     char *getenv(), *strchr();
  253.  
  254.     if (p = getenv("TZNAME")) {
  255.         if (q = strchr(p, ',')) {
  256.             if (dst)
  257.                 return(++q);
  258.             else {
  259.                 *q = '\0';
  260.                 strncpy(czone, p, sizeof(czone)-1);
  261.                 czone[sizeof(czone)-1] = '\0';
  262.                 *q = ',';
  263.                 return (czone);
  264.             }
  265.         }
  266.         return(p);
  267.     }
  268.     for (zp=zonetab; zp->offset!=-1; zp++)
  269.         if (zp->offset==zone) {
  270.             if (dst && zp->dlzone)
  271.                 return(zp->dlzone);
  272.             if (!dst && zp->stdzone)
  273.                 return(zp->stdzone);
  274.         }
  275.     if (zone<0) {
  276.         zone = -zone;
  277.         sign = "+";
  278.     } else
  279.         sign = "-";
  280.     sprintf(czone, "GMT%s%d:%02d", sign, zone/60, zone%60);
  281.     return(czone);
  282. }
  283.  
  284.  
  285. sleep(seconds) unsigned seconds;
  286. {
  287.     long int wakeup = TickCount() + 60*seconds;
  288.     
  289.     for (;;)
  290.     {
  291.         if (TickCount() > wakeup)
  292.             return;
  293.     }
  294. }
  295.  
  296. #if 0
  297. long int getpid()
  298. {
  299.     return (42);
  300. }
  301. #endif
  302.  
  303. long int getuid()
  304. {
  305.     return (0/*root*/);
  306. }
  307.  
  308. struct passwd *getpwent()
  309. {
  310.     return (NULL/*not found*/);
  311. }
  312.  
  313. struct passwd *getpwuid()
  314. {
  315.     return (NULL/*not found*/);
  316. }
  317.  
  318. struct passwd *getpwnam()
  319. {
  320.     return (NULL/*not found*/);
  321. }
  322.  
  323. char *getlogin()
  324. {
  325.     return("macuser");
  326. }
  327.  
  328. int chmod(path, mode)
  329.     char *path;
  330.     int mode;
  331. {
  332. #pragma unused(path)
  333. #pragma unused(mode)
  334.     return(0);
  335. }
  336.  
  337. #if 0
  338. access(path, mode)
  339.     char *path;
  340.     int mode;
  341. {
  342. #pragma unused(path)
  343. #pragma unused(mode)
  344.     return(0);
  345. }
  346.  
  347. char *mktemp(template)
  348.     char *template;
  349. {
  350.     return(template);
  351. }
  352.  
  353. abort()
  354. {
  355.     exit(-1);
  356. }
  357. #endif
  358.  
  359. bzero( b, s)
  360.     char *b;
  361.     long s;
  362. {
  363.     for( ; s ; ++b, --s)
  364.         *b = 0;
  365. }
  366.  
  367. bfill( b, s, fill)
  368.     char *b;
  369.     long s;
  370.     char fill;
  371. {
  372.     for( ; s ; ++b, --s)
  373.         *b = fill;
  374. }
  375.  
  376. bcopy (c1, c2, s)
  377.     char        *c1, *c2;
  378.     long        s;
  379. {
  380.     for ( ; s ; --s)
  381.         *c2++ = *(c1++);
  382. }
  383.  
  384.  
  385. bcmp (c1, c2, s)
  386.     char        *c1, *c2;
  387.     long        s;
  388. {
  389.     for ( ; s ; --s)
  390.         if(*c2++ != *(c1++)) return(1);
  391.     return(0);
  392. }
  393.  
  394. char    *sys_errlist[] = {
  395.     "Error 0",
  396.     "Not owner",                /* 1 - EPERM */
  397.     "No such file or directory",        /* 2 - ENOENT */
  398.     "No such process",            /* 3 - ESRCH */
  399.     "Interrupted system call",        /* 4 - EINTR */
  400.     "I/O error",                /* 5 - EIO */
  401.     "No such device or address",        /* 6 - ENXIO */
  402.     "Arg list too long",            /* 7 - E2BIG */
  403.     "Exec format error",            /* 8 - ENOEXEC */
  404.     "Bad file number",            /* 9 - EBADF */
  405.     "No children",                /* 10 - ECHILD */
  406.     "No more processes",            /* 11 - EAGAIN */
  407.     "Not enough core",            /* 12 - ENOMEM */
  408.     "Permission denied",            /* 13 - EACCES */
  409.     "Bad address",                /* 14 - EFAULT */
  410.     "Block device required",        /* 15 - ENOTBLK */
  411.     "Mount device busy",            /* 16 - EBUSY */
  412.     "File exists",                /* 17 - EEXIST */
  413.     "Cross-device link",            /* 18 - EXDEV */
  414.     "No such device",            /* 19 - ENODEV */
  415.     "Not a directory",            /* 20 - ENOTDIR */
  416.     "Is a directory",            /* 21 - EISDIR */
  417.     "Invalid argument",            /* 22 - EINVAL */
  418.     "File table overflow",            /* 23 - ENFILE */
  419.     "Too many open files",            /* 24 - EMFILE */
  420.     "Not a typewriter",            /* 25 - ENOTTY */
  421.     "Text file busy",            /* 26 - ETXTBSY */
  422.     "File too large",            /* 27 - EFBIG */
  423.     "No space left on device",        /* 28 - ENOSPC */
  424.     "Illegal seek",                /* 29 - ESPIPE */
  425.     "Read-only file system",        /* 30 - EROFS */
  426.     "Too many links",            /* 31 - EMLINK */
  427.     "Broken pipe",                /* 32 - EPIPE */
  428.  
  429. /* math software */
  430.     "Argument too large",            /* 33 - EDOM */
  431.     "Result too large",            /* 34 - ERANGE */
  432.  
  433. /* non-blocking and interrupt i/o */
  434.     "Operation would block",        /* 35 - EWOULDBLOCK */
  435.     "Operation now in progress",        /* 36 - EINPROGRESS */
  436.     "Operation already in progress",    /* 37 - EALREADY */
  437.  
  438. /* ipc/network software */
  439.  
  440.     /* argument errors */
  441.     "Socket operation on non-socket",    /* 38 - ENOTSOCK */
  442.     "Destination address required",        /* 39 - EDESTADDRREQ */
  443.     "Message too long",            /* 40 - EMSGSIZE */
  444.     "Protocol wrong type for socket",    /* 41 - EPROTOTYPE */
  445.     "Protocol not available",        /* 42 - ENOPROTOOPT */
  446.     "Protocol not supported",        /* 43 - EPROTONOSUPPORT */
  447.     "Socket type not supported",        /* 44 - ESOCKTNOSUPPORT */
  448.     "Operation not supported on socket",    /* 45 - EOPNOTSUPP */
  449.     "Protocol family not supported",    /* 46 - EPFNOSUPPORT */
  450.     "Address family not supported by protocol family",
  451.                         /* 47 - EAFNOSUPPORT */
  452.     "Address already in use",        /* 48 - EADDRINUSE */
  453.     "Can't assign requested address",    /* 49 - EADDRNOTAVAIL */
  454.  
  455.     /* operational errors */
  456.     "Network is down",            /* 50 - ENETDOWN */
  457.     "Network is unreachable",        /* 51 - ENETUNREACH */
  458.     "Network dropped connection on reset",    /* 52 - ENETRESET */
  459.     "Software caused connection abort",    /* 53 - ECONNABORTED */
  460.     "Connection reset by peer",        /* 54 - ECONNRESET */
  461.     "No buffer space available",        /* 55 - ENOBUFS */
  462.     "Socket is already connected",        /* 56 - EISCONN */
  463.     "Socket is not connected",        /* 57 - ENOTCONN */
  464.     "Can't send after socket shutdown",    /* 58 - ESHUTDOWN */
  465.     "Too many references: can't splice",    /* 59 - ETOOMANYREFS */
  466.     "Connection timed out",            /* 60 - ETIMEDOUT */
  467.     "Connection refused",            /* 61 - EREFUSED */
  468.     "Too many levels of symbolic links",    /* 62 - ELOOP */
  469.     "File name too long",            /* 63 - ENAMETOOLONG */
  470.     "Host is down",                /* 64 - EHOSTDOWN */
  471.     "Host is unreachable",            /* 65 - EHOSTUNREACH */
  472.     "Directory not empty",            /* 66 - ENOTEMPTY */
  473.     "Too many processes",            /* 67 - EPROCLIM */
  474.     "Too many users",            /* 68 - EUSERS */
  475.     "Disc quota exceeded",            /* 69 - EDQUOT */
  476.     "Stale NFS file handle",        /* 70 - ESTALE */
  477.     "Too many levels of remote in path",    /* 71 - EREMOTE */
  478. };
  479.  
  480. int    sys_nerr = { sizeof sys_errlist/sizeof sys_errlist[0] };
  481.  
  482. /*
  483.  * Copyright (c) 1987 Regents of the University of California.
  484.  * All rights reserved.
  485.  *
  486.  * Redistribution and use in source and binary forms are permitted
  487.  * provided that the above copyright notice and this paragraph are
  488.  * duplicated in all such forms and that any documentation,
  489.  * advertising materials, and other materials related to such
  490.  * distribution and use acknowledge that the software was developed
  491.  * by the University of California, Berkeley.  The name of the
  492.  * University may not be used to endorse or promote products derived
  493.  * from this software without specific prior written permission.
  494.  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
  495.  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
  496.  * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  497.  */
  498.  
  499. #if defined(LIBC_SCCS) && !defined(lint)
  500. static char sccsid[] = "@(#)strcasecmp.c    5.6 (Berkeley) 6/27/88";
  501. #endif /* LIBC_SCCS and not lint */
  502.  
  503. #include <sys/types.h>
  504.  
  505. /*
  506.  * This array is designed for mapping upper and lower case letter
  507.  * together for a case independent comparison.  The mappings are
  508.  * based upon ascii character sequences.
  509.  */
  510. static u_char charmap[] = {
  511.     '\000', '\001', '\002', '\003', '\004', '\005', '\006', '\007',
  512.     '\010', '\011', '\012', '\013', '\014', '\015', '\016', '\017',
  513.     '\020', '\021', '\022', '\023', '\024', '\025', '\026', '\027',
  514.     '\030', '\031', '\032', '\033', '\034', '\035', '\036', '\037',
  515.     '\040', '\041', '\042', '\043', '\044', '\045', '\046', '\047',
  516.     '\050', '\051', '\052', '\053', '\054', '\055', '\056', '\057',
  517.     '\060', '\061', '\062', '\063', '\064', '\065', '\066', '\067',
  518.     '\070', '\071', '\072', '\073', '\074', '\075', '\076', '\077',
  519.     '\100', '\141', '\142', '\143', '\144', '\145', '\146', '\147',
  520.     '\150', '\151', '\152', '\153', '\154', '\155', '\156', '\157',
  521.     '\160', '\161', '\162', '\163', '\164', '\165', '\166', '\167',
  522.     '\170', '\171', '\172', '\133', '\134', '\135', '\136', '\137',
  523.     '\140', '\141', '\142', '\143', '\144', '\145', '\146', '\147',
  524.     '\150', '\151', '\152', '\153', '\154', '\155', '\156', '\157',
  525.     '\160', '\161', '\162', '\163', '\164', '\165', '\166', '\167',
  526.     '\170', '\171', '\172', '\173', '\174', '\175', '\176', '\177',
  527.     '\200', '\201', '\202', '\203', '\204', '\205', '\206', '\207',
  528.     '\210', '\211', '\212', '\213', '\214', '\215', '\216', '\217',
  529.     '\220', '\221', '\222', '\223', '\224', '\225', '\226', '\227',
  530.     '\230', '\231', '\232', '\233', '\234', '\235', '\236', '\237',
  531.     '\240', '\241', '\242', '\243', '\244', '\245', '\246', '\247',
  532.     '\250', '\251', '\252', '\253', '\254', '\255', '\256', '\257',
  533.     '\260', '\261', '\262', '\263', '\264', '\265', '\266', '\267',
  534.     '\270', '\271', '\272', '\273', '\274', '\275', '\276', '\277',
  535.     '\300', '\341', '\342', '\343', '\344', '\345', '\346', '\347',
  536.     '\350', '\351', '\352', '\353', '\354', '\355', '\356', '\357',
  537.     '\360', '\361', '\362', '\363', '\364', '\365', '\366', '\367',
  538.     '\370', '\371', '\372', '\333', '\334', '\335', '\336', '\337',
  539.     '\340', '\341', '\342', '\343', '\344', '\345', '\346', '\347',
  540.     '\350', '\351', '\352', '\353', '\354', '\355', '\356', '\357',
  541.     '\360', '\361', '\362', '\363', '\364', '\365', '\366', '\367',
  542.     '\370', '\371', '\372', '\373', '\374', '\375', '\376', '\377',
  543. };
  544.  
  545. strcasecmp(s1, s2)
  546.     char *s1, *s2;
  547. {
  548.     register u_char    *cm = charmap,
  549.             *us1 = (u_char *)s1,
  550.             *us2 = (u_char *)s2;
  551.  
  552.     while (cm[*us1] == cm[*us2++])
  553.         if (*us1++ == '\0')
  554.             return(0);
  555.     return(cm[*us1] - cm[*--us2]);
  556. }
  557.  
  558. strncasecmp(s1, s2, n)
  559.     char *s1, *s2;
  560.     register int n;
  561. {
  562.     register u_char    *cm = charmap,
  563.             *us1 = (u_char *)s1,
  564.             *us2 = (u_char *)s2;
  565.  
  566.     while (--n >= 0 && cm[*us1] == cm[*us2++])
  567.         if (*us1++ == '\0')
  568.             return(0);
  569.     return(n < 0 ? 0 : cm[*us1] - cm[*--us2]);
  570. }
  571.